﻿using Opc.Ua;
using Opc.Ua.Client;
using SHRIS.MIS.Common.Util.Extension;
using SHRIS.MIS.Entity.ScadaBaseInfo;
using SHRIS.MIS.Entity.ScadaData;
using SHRIS.MIS.Service.OpcService;
using System;
using System.Collections;
using System.Collections.Generic;
using System.Linq;
using System.Text;

namespace SHRIS.MIS.Service.Device
{
    public class LaserMark_06 : BasicDevice
    {
        private readonly IEnumerable<OpcDataSourceEntity> _opcDataSourceEntities;
        public LaserMark_06(DeviceEntity deviceEntity,
           WorkshopCommunicationService workshopCommunicationService,
           IEnumerable<OpcDataSourceEntity> opcDataSourceEntities)
           : base(deviceEntity, workshopCommunicationService)
        {
            _opcDataSourceEntities = opcDataSourceEntities;
            CheckOutDataType();
        }

        private void CheckOutDataType()
        {
            //对所有OPC 数据类型进行校验，如果不对记入LOG

        }
        public override void InitalDevice()
        {
            //创建opc 订阅

            //找出该通道下的订阅数据，dataAction==4 为订阅
            var subscriptionDatas = _opcDataSourceEntities.Where(i => i.DataAction == 4);

            //找出订阅数据的服务器列表
            var serverIds = subscriptionDatas.Select(i => i.ServerId).Distinct().ToList();

            if (serverIds.Count() == 1)
            {
                _workshopCommunicationService.CreateOpcSubscription(subscriptionDatas, DataHandler);
            }


            //用deviceCode作为订阅组名字
            //var subscriptionName = _deviceEntity.DeviceCode;

        }

        private void DataHandler(MonitoredItem monitoredItem, MonitoredItemNotificationEventArgs e)
        {
            try
            {
                MonitoredItemNotification notification = e.NotificationValue as MonitoredItemNotification;
                //Console.WriteLine(notification.Value.StatusCode.ToString());

                if (notification != null)
                {
                    Guid dataId = new Guid();
                    bool isId = Guid.TryParse(monitoredItem.DisplayName, out dataId);
                    if (isId && (!dataId.IsGuidNullOrEmpty()))
                    {
                        var dataSource = _opcDataSourceEntities.Where(i => i.Id == dataId).First();
                        switch (dataSource.DataName)
                        {
                            case "InitStatus":
                                {
                                    InitStatus = (bool)notification.Value.Value;
                                    break;
                                }
                            case "StartMarkStatus":
                                {
                                    StartMarkStatus = (bool)notification.Value.Value;
                                    break;
                                }
                            case "CodeBypassStatus":
                                {
                                    CodeBypassStatus = (bool)notification.Value.Value;
                                    break;
                                }
                            case "EMO":
                                {
                                    EMO = (bool)notification.Value.Value;
                                    break;
                                }
                            case "Ready":
                                {
                                    Ready = (bool)notification.Value.Value;
                                    break;
                                }
                            case "End":
                                {
                                    End = (bool)notification.Value.Value;
                                    break;
                                }
                            case "HasWorkpiece":
                                {
                                    HasWorkpiece = (bool)notification.Value.Value;
                                    break;
                                }
                            case "Com":
                                {
                                    Com = (bool)notification.Value.Value;
                                    break;
                                }
                            case "InitSuccess":
                                {
                                    InitSuccess = (bool)notification.Value.Value;
                                    break;
                                }
                            case "MarkComplete":
                                {
                                    MarkComplete = (bool)notification.Value.Value;
                                    break;
                                }
                            case "WorkpieceSource":
                                {
                                    WorkpieceSource = (short)notification.Value.Value;
                                    break;
                                }
                            case "MarkContent_Enter":
                                {
                                    if (notification.Value.Value != null)
                                    {
                                        MarkContent_Enter = notification.Value.Value.ToString();
                                    }

                                    break;
                                }
                            case "Result":
                                {
                                    if (notification.Value.Value != null)
                                    {
                                        Result = notification.Value.Value.ToString();
                                    }

                                    break;
                                }
                            case "MaterialCode":
                                {
                                    if (notification.Value.Value != null)
                                    {
                                        MaterialCode = notification.Value.Value.ToString();
                                    }
                                    break;
                                }
                            case "ValAct":
                                {
                                    ValAct = (bool)notification.Value.Value;
                                    break;
                                }
                            case "PriEquStaW":
                                {
                                    if (notification.Value.Value != null)
                                    {
                                        ushort _value = (ushort)notification.Value.Value;
                                        byte[] b = BitConverter.GetBytes(_value);
                                        PriEquStaW = new BitArray(b);
                                    }
                                    break;
                                }
                            case "PriEquProStaW":
                                {
                                    if (notification.Value.Value != null)
                                    {
                                        ushort _value = (ushort)notification.Value.Value;
                                        byte[] b = BitConverter.GetBytes(_value);
                                        PriEquProStaW = new BitArray(b);
                                    }
                                    break;
                                }
                            case "PriEquAlarmW_1":
                                {
                                    if (notification.Value.Value != null)
                                    {
                                        ushort _value = (ushort)notification.Value.Value;
                                        byte[] b = BitConverter.GetBytes(_value);
                                        PriEquAlarmW_1 = new BitArray(b);
                                    }
                                    break;
                                }
                            case "PriEquAlarmW_2":
                                {
                                    if (notification.Value.Value != null)
                                    {
                                        ushort _value = (ushort)notification.Value.Value;
                                        byte[] b = BitConverter.GetBytes(_value);
                                        PriEquAlarmW_2 = new BitArray(b);
                                    }
                                    break;
                                }
                            case "PriEquStartEquTime":
                                {
                                    if (notification.Value.Value != null)
                                    {
                                        PriEquStartEquTime = DateTimeOffset.Parse(notification.Value.Value.ToString());
                                    }
                                    break;
                                }
                            case "PriEquRunningTime":
                                {
                                    if (notification.Value.Value != null)
                                    {
                                        PriEquRunningTime = Double.Parse(notification.Value.Value.ToString());
                                    }
                                    break;
                                }
                            case "DataPatternError":
                                {
                                    DataPatternError = (bool)notification.Value.Value;
                                    break;
                                }
                            case "InitFailed":
                                {
                                    InitFailed = (bool)notification.Value.Value;
                                    break;
                                }
                            case "MarkFailed":
                                {
                                    MarkFailed = (bool)notification.Value.Value;
                                    break;
                                }
                            default:
                                {
                                    break;
                                }
                        }
                    }

                }
            }
            catch (Exception ex)
            {
                throw ex;
            }
        }

        #region 设备参数

        private bool dataPatternError;
        /// <summary>
        /// 打标机数据非法或格式不正常
        /// </summary>
        public bool DataPatternError
        {
            get
            {
                return dataPatternError;
            }
            set
            {
                bool previewVlaue = dataPatternError;
                dataPatternError = value;
                OnPropertyChanged("DataPatternError", previewVlaue, dataPatternError);
            }
        }

        private bool initFailed;
        /// <summary>
        /// 打标机初始化失败
        /// </summary>
        public bool InitFailed
        {
            get
            {
                return initFailed;
            }
            set
            {
                bool previewVlaue = initFailed;
                initFailed = value;
                OnPropertyChanged("InitFailed", previewVlaue, initFailed);
            }
        }

        private bool markFailed;
        /// <summary>
        /// 打标失败
        /// </summary>
        public bool MarkFailed
        {
            get
            {
                return markFailed;
            }
            set
            {
                bool previewVlaue = markFailed;
                markFailed = value;
                OnPropertyChanged("MarkFailed", previewVlaue, markFailed);
            }
        }

        private BitArray priEquStaW;
        /// <summary>
        /// 打码设备状态字
        /// DB7.DBB640
        /// </summary>
        public BitArray PriEquStaW
        {
            get
            {
                return priEquStaW;
            }
            set
            {
                BitArray previewVlaue = priEquStaW;
                priEquStaW = value;
                OnPropertyChanged("PriEquStaW", previewVlaue, priEquStaW);
            }
        }

        private BitArray priEquProStaW;
        /// <summary>
        /// 打码程序状态字
        /// DB7.DBB642
        /// </summary>
        public BitArray PriEquProStaW
        {
            get
            {
                return priEquProStaW;
            }
            set
            {
                BitArray previewVlaue = priEquProStaW;
                priEquProStaW = value;
                OnPropertyChanged("PriEquProStaW", previewVlaue, priEquProStaW);
            }
        }

        private BitArray priEquAlarmW_1;
        /// <summary>
        /// 打码设备报警字1
        /// DB7.DBB644
        /// </summary>
        public BitArray PriEquAlarmW_1
        {
            get
            {
                return priEquAlarmW_1;
            }
            set
            {
                BitArray previewVlaue = priEquAlarmW_1;
                priEquAlarmW_1 = value;
                OnPropertyChanged("PriEquAlarmW_1", previewVlaue, priEquAlarmW_1);
            }
        }

        private BitArray priEquAlarmW_2;
        /// <summary>
        /// 打码设备报警字2
        /// DB7.DBB646
        /// </summary>
        public BitArray PriEquAlarmW_2
        {
            get
            {
                return priEquAlarmW_2;
            }
            set
            {
                BitArray previewVlaue = priEquAlarmW_2;
                priEquAlarmW_2 = value;
                OnPropertyChanged("PriEquAlarmW_2", previewVlaue, priEquAlarmW_2);
            }
        }

        private DateTimeOffset priEquStartEquTime;
        /// <summary>
        /// 打码设备本次开机时刻
        /// DB7.DBB690
        /// </summary>
        public DateTimeOffset PriEquStartEquTime
        {
            get
            {
                return priEquStartEquTime;
            }
            set
            {
                DateTimeOffset previewVlaue = priEquStartEquTime;
                priEquStartEquTime = value;
                OnPropertyChanged("PriEquStartEquTime", previewVlaue, priEquStartEquTime);
            }
        }

        private double priEquRunningTime;
        /// <summary>
        /// 打码设备开机时间，永不清零（单位:小时）
        /// DB7.DBD698
        /// </summary>
        public double PriEquRunningTime
        {
            get
            {
                return priEquRunningTime;
            }
            set
            {
                double previewVlaue = priEquRunningTime;
                priEquRunningTime = value;
                OnPropertyChanged("PriEquRunningTime", previewVlaue, priEquRunningTime);
            }
        }

        private bool startScanCodeStatus;
        public bool StartScanCodeStatus
        {
            get
            {
                return startScanCodeStatus;
            }
            set
            {
                bool previewVlaue = startScanCodeStatus;
                startScanCodeStatus = value;
                OnPropertyChanged("StartScanCodeStatus", previewVlaue, startScanCodeStatus);
            }
        }

        private bool initStatus;
        public bool InitStatus
        {
            get
            {
                return initStatus;
            }
            set
            {
                bool previewVlaue = initStatus;
                initStatus = value;
                OnPropertyChanged("InitStatus", previewVlaue, initStatus);
            }
        }

        private bool startMarkStatus;
        public bool StartMarkStatus
        {
            get
            {
                return startMarkStatus;
            }
            set
            {
                bool previewVlaue = startMarkStatus;
                startMarkStatus = value;
                OnPropertyChanged("StartMarkStatus", previewVlaue, startMarkStatus);
            }
        }

        private bool codeBypassStatus;
        public bool CodeBypassStatus
        {
            get
            {
                return codeBypassStatus;
            }
            set
            {
                bool previewVlaue = codeBypassStatus;
                codeBypassStatus = value;
                OnPropertyChanged("CodeBypassStatus", previewVlaue, codeBypassStatus);
            }
        }

        private bool eMO;
        public bool EMO
        {
            get
            {
                return eMO;
            }
            set
            {
                bool previewVlaue = eMO;
                eMO = value;
                OnPropertyChanged("EMO", previewVlaue, eMO);
            }
        }

        private bool ready;
        public bool Ready
        {
            get
            {
                return ready;
            }
            set
            {
                bool previewVlaue = ready;
                ready = value;
                OnPropertyChanged("Ready", previewVlaue, ready);
            }
        }

        private bool end;
        public bool End
        {
            get
            {
                return end;
            }
            set
            {
                bool previewVlaue = end;
                end = value;
                OnPropertyChanged("End", previewVlaue, end);
            }
        }

        private bool sasWorkpiece;
        public bool HasWorkpiece
        {
            get
            {
                return sasWorkpiece;
            }
            set
            {
                bool previewVlaue = sasWorkpiece;
                sasWorkpiece = value;
                OnPropertyChanged("HasWorkpiece", previewVlaue, sasWorkpiece);
            }
        }

        private bool com;
        public bool Com
        {
            get
            {
                return com;
            }
            set
            {
                bool previewVlaue = com;
                com = value;
                OnPropertyChanged("Com", previewVlaue, com);
            }
        }

        private bool initSuccess;
        public bool InitSuccess
        {
            get
            {
                return initSuccess;
            }
            set
            {
                bool previewVlaue = initSuccess;
                initSuccess = value;
                OnPropertyChanged("InitSuccess", previewVlaue, initSuccess);
            }
        }

        private bool markComplete;
        public bool MarkComplete
        {
            get
            {
                return markComplete;
            }
            set
            {
                bool previewVlaue = markComplete;
                markComplete = value;
                OnPropertyChanged("MarkComplete", previewVlaue, markComplete);
            }
        }

        private short workpieceSource;
        public short WorkpieceSource
        {
            get
            {
                return workpieceSource;
            }
            set
            {
                short previewVlaue = workpieceSource;
                workpieceSource = value;
                OnPropertyChanged("WorkpieceSource", previewVlaue, workpieceSource);
            }
        }

        private string markContent_Enter;
        public string MarkContent_Enter
        {
            get
            {
                return markContent_Enter;
            }
            set
            {
                string previewVlaue = markContent_Enter;
                markContent_Enter = value;
                OnPropertyChanged("MarkContent_Enter", previewVlaue, markContent_Enter);
            }
        }

        private string result;
        public string Result
        {
            get
            {
                return result;
            }
            set
            {
                string previewVlaue = result;
                result = value;
                OnPropertyChanged("Result", previewVlaue, result);
            }
        }

        private string materialCode;
        public string MaterialCode
        {
            get
            {
                return materialCode;
            }
            set
            {
                string previewVlaue = materialCode;
                materialCode = value;
                OnPropertyChanged("MaterialCode", previewVlaue, materialCode);
            }
        }

        private bool valAct;
        public bool ValAct
        {
            get
            {
                return valAct;
            }
            set
            {
                bool previewVlaue = valAct;
                valAct = value;
                OnPropertyChanged("ValAct", previewVlaue, valAct);
            }
        }
        #endregion
    }
}
